using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
using UniversalAdmin.Domain.Common;
using UniversalAdmin.Domain.Events;

namespace UniversalAdmin.Domain.Entities;

[Table("roles")]
public class Role : AggregateRoot
{
  [Required]
  [MaxLength(50)]
  [Column("name")]
  public string Name { get; private set; } = null!;

  [Column("description")]
  public string? Description { get; private set; }

  // 导航属性
  public virtual ICollection<UserRole> UserRoles { get; set; } = new List<UserRole>();
  public virtual ICollection<RoleMenu> RoleMenus { get; set; } = new List<RoleMenu>();

  // 构造函数
  protected Role() { }

  // 工厂方法
  public static Role Create(string name, string? description)
  {
    if (string.IsNullOrWhiteSpace(name))
      throw new ArgumentException("角色名称不能为空", nameof(name));

    var role = new Role
    {
      Name = name,
      Description = description
    };

    role.AddDomainEvent(new RoleCreatedEvent(role));
    return role;
  }

  // 领域方法
  public void Update(string newName, string? newDescription, bool isActive, IEnumerable<Menu> menus)
  {
    // 验证超级管理员角色名称不能修改
    if (Name == "SuperAdmin" && newName != "SuperAdmin")
    {
      throw new InvalidOperationException("超级管理员角色名称不能修改");
    }

    Name = newName;
    Description = newDescription;
    IsActive = isActive;
    UpdatedAt = DateTime.UtcNow;

    // 更新菜单权限
    UpdateMenus(menus);

    // 领域事件在内部添加
    AddDomainEvent(new RoleUpdatedEvent(this));
  }

  private void UpdateMenus(IEnumerable<Menu> menus)
  {
    RoleMenus.Clear();
    foreach (var menu in menus)
    {
      RoleMenus.Add(new RoleMenu { Role = this, Menu = menu });
    }
  }

  public void AssignMenus(IEnumerable<Menu> menus)
  {
    RoleMenus.Clear();
    foreach (var menu in menus)
    {
      RoleMenus.Add(new RoleMenu { Role = this, Menu = menu });
    }
  }

  public bool CanBeDeleted()
  {
    if (Name == "SuperAdmin")
      return false;

    return !UserRoles.Any();
  }

  public void Delete()
  {
    // 检查是否是超级管理员角色
    if (Name == "SuperAdmin")
    {
      throw new InvalidOperationException("不能删除超级管理员角色");
    }

    // 检查是否有用户使用该角色
    if (UserRoles.Any())
    {
      throw new InvalidOperationException("该角色已被用户使用，不能删除");
    }

    // 添加领域事件（在聚合根内部添加）
    AddDomainEvent(new RoleDeletedEvent(Id, Name));
  }
}